package com.ishow.bs.utils;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;

import org.apache.log4j.Logger;

/**
 * 构造的一个请求类，用来防止sql注入和xss攻击 getParameter方法、getParameterValues方法重写了
 * 其他方法还是用request以前的值，子类的Map数据有增加，request实际没增加，
 * 当你获取getParameterMap、getParameterNames这些方法的时候，参数就又有问题了，会不一致
 * 当然，最直接的解决方法是将这些方法也给换掉，也没问题
 * 
 * @author chichi
 */
public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper {
	private static Logger log = Logger.getLogger(XssHttpServletRequestWrapper.class);

	public XssHttpServletRequestWrapper(HttpServletRequest servletRequest) {
		super(servletRequest);
	}

	public String[] getParameterValues(String parameter) {
		String[] values = super.getParameterValues(parameter);
		if (values == null) {
			return null;
		}
		int count = values.length;
		String[] encodedValues = new String[count];
		for (int i = 0; i < count; i++) {
			String beforeValue = values[i];
			encodedValues[i] = cleanXSS(values[i]);
			if (!beforeValue.equals(encodedValues[i])) {
				log.warn("[XSS过滤器]防攻击生效，请求参数：[" + parameter + ":" + beforeValue + "] -> [" + parameter + ":"
						+ encodedValues[i] + "]");
			}
		}
		return encodedValues;
	}

	public String getParameter(String parameter) {
		String beforeValue = super.getParameter(parameter);
		if (beforeValue == null) {
			return null;
		}
		String value = cleanXSS(beforeValue);
		if (!beforeValue.equals(value)) {
			log.warn("[XSS过滤器]防攻击生效，请求参数：[" + parameter + ":" + beforeValue + "] -> [" + parameter + ":" + value + "]");
		}
		return value;
	}

	public String getHeader(String name) {
		String beforeValue = super.getHeader(name);
		if (beforeValue == null)
			return null;
		String value = cleanXSS(beforeValue);
		if (!beforeValue.equals(value)) {
			log.warn("[XSS过滤器]防攻击生效，请求参数：[" + name + ":" + beforeValue + "] -> [" + name + ":" + value + "]");
		}
		return value;
	}

	private String cleanXSS(String value) {
		value = value.replaceAll("<", "&lt;").replaceAll(">", "&gt;");
		value = value.replaceAll("\\(", "&#40;").replaceAll("\\)", "&#41;");
		value = value.replaceAll("'", "&#39;");
		value = value.replaceAll("eval\\((.*)\\)", "");
		value = value.replaceAll("[\\\"\\\'][\\s]*javascript:(.*)[\\\"\\\']", "\"\"");
		value = value.replaceAll("script", "");
		return value;
	}

}